/*
 * Copyright (C) 2018 xuexiangjys(xuexiangjys@163.com)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.sj.parksdk.net.http.interceptor;

import android.annotation.SuppressLint;

import com.sj.parksdk.core.http.subscriber.TipRequestSubscriber;
import com.sj.parksdk.net.http.ApiHelper;
import com.sj.parksdk.net.manager.TokenManager;
import com.sj.parksdk.net.result.databean.Data_Token;
import com.xuexiang.xhttp2.XHttp;
import com.xuexiang.xhttp2.exception.ApiException;
import com.xuexiang.xhttp2.interceptor.BaseExpiredInterceptor;
import com.xuexiang.xhttp2.logs.HttpLog;
import com.xuexiang.xhttp2.model.ExpiredInfo;
import com.xuexiang.xhttp2.request.CustomRequest;
import com.xuexiang.xrouter.launcher.XRouter;
import com.xuexiang.xutil.data.DateUtils;
import com.xuexiang.xutil.net.JSONUtils;
import com.xuexiang.xutil.tip.ToastUtils;

import java.io.IOException;

import okhttp3.Response;


/**
 * 处理各种失效响应处理：包括token过期、账号异地登录、时间戳过期、签名sign错误等
 *
 * @author xuexiang
 * @since 2018/8/7 上午9:41
 */
public class CustomExpiredInterceptor extends BaseExpiredInterceptor {

    /**
     * 请求失败,toast message
     */
    public static final int REQUEST_FAIL = 400;


    /**
     * Token失效，需要重新获取token的code码,认证失败,缺少Token,无权限，未注册/未登陆
     */
    public static final int TOKEN_INVALID = 401;
    /**
     * 无权限
     */
    public static final int TOKEN_MISSING = TOKEN_INVALID + 2;

    public static final int SERVER_ERROR = 500;

    @Override
    protected ExpiredInfo isResponseExpired(Response oldResponse, String bodyString) {
        int code = JSONUtils.getInt(bodyString.toLowerCase(), "code", 0);
        ExpiredInfo expiredInfo = new ExpiredInfo(code);
        switch (code) {
            case REQUEST_FAIL:
                expiredInfo.setExpiredType(ExpiredType.KEY_REQUEST_FAIL)
                        .setBodyString(bodyString);
                break;
            case TOKEN_INVALID:
                expiredInfo.setExpiredType(ExpiredType.KEY_TOKEN_EXPIRED)
                        .setBodyString(bodyString);
            case TOKEN_MISSING:
                expiredInfo.setExpiredType(ExpiredType.KEY_UNREGISTERED_USER)
                        .setBodyString(bodyString);
                break;
            case SERVER_ERROR:
                expiredInfo.setExpiredType(ExpiredType.KEY_SERVER_ERROR)
                        .setBodyString(bodyString);
                break;
            default:
                break;
        }
        return expiredInfo;
    }

    @SuppressLint("CheckResult")
    @Override
    protected Response responseExpired(Response oldResponse, Chain chain, ExpiredInfo expiredInfo) {
        switch(expiredInfo.getExpiredType()) {
//            case ExpiredType.KEY_REQUEST_FAIL:
//                String msg = JSONUtils.getString(expiredInfo.getBodyString().toLowerCase(), "message","请求失败,请稍后再试");
//                ToastUtils.toast(msg);
//                break;
            case ExpiredType.KEY_UNREGISTERED_USER:
                String msg2 = JSONUtils.getString(expiredInfo.getBodyString().toLowerCase(), "message","无权限");
                ToastUtils.toast(msg2);
                break;
            case ExpiredType.KEY_SERVER_ERROR:
                String msg3 = JSONUtils.getString(expiredInfo.getBodyString().toLowerCase(), "message","服务器错误");
                ToastUtils.toast(msg3);
                break;
            case ExpiredType.KEY_TOKEN_EXPIRED:
                //access_token超时
                return keyTokenExpired(chain);
            default:
                break;
        }
        return null;
    }

    private Response keyTokenExpired(Chain chain) {
        if(DateUtils.getNowMills()>TokenManager.getInstance().getTokenExpiresOn()*1000){
            return refreshToken(chain);
        }else{
            return null;
        }
    }

    @SuppressLint("CheckResult")
    private Response refreshToken(Chain chain) {
        final boolean[] isRefreshToken = {false};
        CustomRequest request = XHttp.custom();
        request.apiCall(ApiHelper.getInstance(request).refreshToken()).subscribeWith(new TipRequestSubscriber<Data_Token>() {
            @Override
            protected void onSuccess(Data_Token data) {
                TokenManager.getInstance().setToken(data.getAccess_token());
                TokenManager.getInstance().setTokenExpiresOn(data.getExpires_on());
                HttpLog.e("token刷新成功：" + data.getAccess_token());
                isRefreshToken[0] = true;
            }

            @Override
            public void onError(ApiException e) {
                XRouter.getInstance()
                        .build("/login/login")
                        .navigation();
//                PageOption.to(LoginFragment.class).setNewActivity(true).
            }
        });
        if(isRefreshToken[0]){
            try {
                HttpLog.e("使用新的token重新进行请求...");

                return chain.proceed(chain.request().newBuilder().removeHeader("Authorization").addHeader("Authorization",TokenManager.getInstance().getToken()).build());
//                return chain.proceed(HttpUtils.updateUrlParams(chain.request(), "token", TokenManager.getInstance().getToken()));
            } catch (IOException e) {
                e.printStackTrace();
            }
        }else{
            return null;
        }
        return null;
    }

    /**
     * 失效类型
     */
    static final class ExpiredType {

        static final int KEY_REQUEST_FAIL = 9;

        /**
         * token失效
         */
        static final int KEY_TOKEN_EXPIRED = 10;

        /**
         * 未注册的用户/无权限
         */
        static final int KEY_UNREGISTERED_USER = KEY_TOKEN_EXPIRED + 1;

        static final int KEY_SERVER_ERROR = 12;
    }
}
